package cn.ilikes.tools.hbase.clients;

import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;

import javax.persistence.EntityManager;
import javax.persistence.Query;

import org.slf4j.Logger;

import cn.ilikes.tools.logs.Loggerfactory;

/**
 * 
 * @author fack
 * 
 */
public abstract class HBaseClientService extends HbaseEntrtyService implements IHBaseClientService {

	private static Logger logger = Loggerfactory.instance(HBaseClientService.class);

	@Override
	public <V> void save(V value) throws HbaseClientServiceException {
		try {
			Loggerfactory.debug(logger, " save entitry : " + value);
			EntityManager em = getEntityManager();
			em.persist(value);
		} catch (RuntimeException e) {
			Loggerfactory.error(logger, e.getMessage(), e);
			throw new HbaseClientServiceException(e);
		}

	}

	@Override
	public <V> void update(V value) throws HbaseClientServiceException {
		try {
			Loggerfactory.debug(logger, " update  entitry : " + value);
			EntityManager em = getEntityManager();
			em.merge(value);
		} catch (RuntimeException e) {
			Loggerfactory.error(logger, e.getMessage(), e);
			throw new HbaseClientServiceException(e);
		}

	}

	@Override
	public <V> void delect(V value) throws HbaseClientServiceException {
		try {
			Loggerfactory.debug(logger, " remove  entitry : " + value);
			EntityManager em = getEntityManager();
			em.remove(em);
		} catch (RuntimeException e) {
			Loggerfactory.error(logger, e.getMessage(), e);
			throw new HbaseClientServiceException(e);
		}

	}

	@Override
	public <K, V> V get(K key, Class<V> clazz) throws HbaseClientServiceException {
		try {
			Loggerfactory.debug(logger, " GET   entitry : " + clazz + " key : " + key);
			EntityManager em = getEntityManager();
			V v = em.find(clazz, key);
			return v;
		} catch (RuntimeException e) {
			Loggerfactory.error(logger, e.getMessage(), e);
			throw new HbaseClientServiceException(e);
		}
	}

	@Override
	public <V> List<V> findBySQL(String hbaseSQL, Map<String, Object> values, int... rowsAndMaxResults) throws HbaseClientServiceException {
		EntityManager em = getEntityManager();
		Query query = em.createQuery(hbaseSQL);
		return excQuery(query, values, rowsAndMaxResults);
	}

	@SuppressWarnings("unchecked")
	private <T> List<T> excQuery(Query query, Map<String, Object> values, int... rowsAndMaxResults) throws HbaseClientServiceException {
		if (values != null) {
			for (Iterator<Entry<String, Object>> entrys = values.entrySet().iterator(); entrys.hasNext();) {
				Entry<String, Object> entry = entrys.next();
				Object value = entry.getValue();
				query = query.setParameter(entry.getKey(), value);
			}
		}
		int leght = rowsAndMaxResults.length;
		if (leght > 0) {
			if (leght == 1) {
				int first = rowsAndMaxResults[0];
				if (first < 0)
					throw new HbaseClientServiceException("  sql  First Result  < 0 ");
				query = query.setFirstResult(rowsAndMaxResults[0]);
			} else if (leght == 2) {
				int first = rowsAndMaxResults[0];
				int max = rowsAndMaxResults[1];
				if (first < 0 || max < 0)
					throw new HbaseClientServiceException(" find sql First Result  < 0  or max <0");
				query = query.setFirstResult(first);
				query = query.setMaxResults(max);
			} else if (leght > 2)
				throw new HbaseClientServiceException(" find sql First  leght ==2  ;first is  start ; ");
		}

		return query.getResultList();
	}

	@Override
	public <V> List<V> findByNameQuery(String name, Map<String, Object> value, int... startAndmaxResults) throws HbaseClientServiceException {
		EntityManager em = getEntityManager();
		Query query = em.createNamedQuery(name);
		return excQuery(query, value, startAndmaxResults);
	}

}
